﻿using NineSeas.Services;
using Orchard;
using Orchard.DisplayManagement;
using Orchard.ContentManagement;
using Orchard.Mvc;
using Orchard.Themes;
using System;
using System.Web.Mvc;
using System.Linq;
using NineSeas.Models;
using Contrib.Voting.Services;
using Orchard.Localization;
using Orchard.Data;
using Contrib.Voting.Models;
using NineSeas.ViewModels;
using System.Collections.Generic;
using Contrib.Taxonomies.Services;
using NineSeas.Extensions;

namespace NineSeas.Controllers
{
    public class BookViewController : Controller
    {
        private const int _defaultTocPagesize = 50;
        private dynamic Shape {get; set;}
        private readonly IOrchardServices _services;
        private readonly IBookService _bookService;
        private readonly IAuthorService _authorService;
        private readonly IChapterService _chapterService;
        private readonly IVotingService _votingService;
        private readonly ISocialStatisticService _socialStatisticService;
        private readonly ITaxonomyService _taxonomyService;
        private Localizer T { get; set; }

        public BookViewController(IOrchardServices services, 
            IBookService bookService, 
            IAuthorService authorService,
            IChapterService chapterService,
            IVotingService votingService,
            ISocialStatisticService socialStatisticService,
            IShapeFactory shapeFactory,
            ITaxonomyService taxonomyService)
        {
            Shape = shapeFactory;
            this._services = services;
            this._bookService = bookService;
            this._authorService = authorService;
            this._chapterService = chapterService;
            this._votingService = votingService;
            this._socialStatisticService = socialStatisticService;
            this._taxonomyService = taxonomyService;
            T = NullLocalizer.Instance;
        }

        [Themed]
        public ActionResult List(BookSearchViewModel search, int currentPage = 0, int pageSize = 18)
        {
            return List(search, new PaginationInfo(currentPage, pageSize));
        }

        private ActionResult List(BookSearchViewModel search, PaginationInfo paging)
        {
            var books = _bookService.Search(search, paging);

            var taxonomy = _taxonomyService.GetTaxonomyByName(Constants.Taxonomies.Categories);
            var categories = _taxonomyService.GetTerms(taxonomy.Id);

            _services.WorkContext.Layout.Zones["Featured"].Add(_services.New.Controls_CategoryMenu(Categories: categories, GroupItemCount: 11), "0");
            _services.WorkContext.Layout.Zones["Featured"].Add(_services.New.BookView_List_Commands(Search: search), "1");
            return new ShapeResult(this, _services.New.BookView_List(
                    Books: books,
                    Paging: paging,
                    Search: search
                ));
        }

        [Themed]
        public ActionResult Index(string name)
        {
            BookPart bookPart = null;
            AuthorProfilePart author = null;
            IList<ChapterPart> chapters = null;
            dynamic first = null;
            if (!String.IsNullOrEmpty(name))
            {
                bookPart = _bookService.GetByName(name);
                author = _authorService.Get(bookPart.AuthorId);
                chapters = _chapterService.GetByBookId(bookPart.Id);
                first = _chapterService.GetFirst(bookPart.Id);
                _socialStatisticService.UpdateViews(bookPart);
            }
            return new ShapeResult(this, _services.New.Book_Index(
                    Settings: _services.WorkContext.CurrentSite.As<NineSeasSettingsPart>(),
                    Book: bookPart,
                    Author: author,
                    Chapters: chapters,
                    First: first,
                    IsLiked: bookPart != null && _socialStatisticService.IsLiked(bookPart)
                ));
        }

        [Themed]
        public ActionResult Toc(string name, int? pageIndex, int? pageSize)
        {
            BookPart bookPart = null;
            AuthorProfilePart author = null;
            dynamic chapters = null;
            dynamic first = null;
            var paging = new PaginationInfo(pageIndex.HasValue ? pageIndex.Value : 0, pageSize.HasValue ? pageSize.Value : _defaultTocPagesize);

            if (!String.IsNullOrEmpty(name))
            {
                bookPart = _bookService.GetByName(name);
                author = _authorService.Get(bookPart.AuthorId); 
                chapters = _chapterService.GetToc(bookPart.Id, paging);
                first = _chapterService.GetFirst(bookPart.Id);

                _socialStatisticService.UpdateViews(bookPart);
            }
            return new ShapeResult(this, _services.New.Book_Toc(
                    Book: bookPart,
                    Author: author,
                    Settings: _services.WorkContext.CurrentSite.As<NineSeasSettingsPart>(),
                    Chapters: chapters,
                    First: first,
                    Paging: paging,
                    IsLiked: bookPart != null && _socialStatisticService.IsLiked(bookPart)
                ));
        }
        [Themed]
        public ActionResult Chapter(string name, int? chapterIndex)
        {
            BookPart bookPart = null;
            AuthorProfilePart author = null;
            IList<ChapterPart> chapters = null;
            dynamic chapter = null;
            if (!String.IsNullOrEmpty(name))
            {
                bookPart = _bookService.GetByName(name);
                author = _authorService.Get(bookPart.AuthorId);
                chapter = _chapterService.GetView(bookPart.Id, chapterIndex);
                chapters = _chapterService.GetByBookId(bookPart.Id);
                _socialStatisticService.UpdateViews(bookPart);
            }

            return new ShapeResult(this, _services.New.Book_Chapter(
                    Book: bookPart,
                    Author: author,
                    Settings: _services.WorkContext.CurrentSite.As<NineSeasSettingsPart>(),
                    Chapter: chapter,
                    Chapters: chapters,
                    IsLiked: bookPart != null && _socialStatisticService.IsLiked(bookPart)
                ));
        }

        public JsonResult Like(string name, string like)
        {
            try
            {
                var bookPart = _bookService.GetByName(name);
                _socialStatisticService.UpdateLikes(bookPart, "1".Equals(like));
                return this.Json(new { success = true, caption = "1".Equals(like) ? T("Liked").Text : T("Like").Text }, JsonRequestBehavior.AllowGet);
            }
            catch
            {
                return this.Json(new { success = false }, JsonRequestBehavior.AllowGet);
            }
        }
    }
}